{{/*
Copyright 2017 syzkaller project authors. All rights reserved.
Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file.
*/}}

{{/* Common page head part, invoked with *uiHeader */}}
{{define "head"}}
	<link rel="stylesheet" href="/static/style.css"/>
	{{if .Redirects}}
		<script>
			{{range $redir := .Redirects}}
				if (window.location.hash == "{{$redir.From}}") {
					window.location.href = "{{$redir.To}}";
				}
			{{end}}
		</script>
	{{end}}
	<script src="/static/common.js"></script>
	{{if .AnalyticsTrackingID}}
		<script async src="https://www.googletagmanager.com/gtag/js?id={{.AnalyticsTrackingID}}"></script>
		<script>
			window.dataLayer = window.dataLayer || [];
			function gtag() { dataLayer.push(arguments); }
			gtag('js', new Date());
			gtag('config', '{{.AnalyticsTrackingID}}');
		</script>
	{{end}}
{{end}}

{{/* Common page header, invoked with *uiHeader */}}
{{define "header"}}
	<header id="topbar">
		<table class="position_table">
			<tr>
				<td>
					<h1><a href="/{{$.Namespace}}">syzbot</a></h1>
					<select class="namespace" onchange="window.location.href = '/' + this.value + '{{.Subpage}}';">
						{{range $ns := .Namespaces}}
							<option value="{{$ns.Name}}" {{if eq $.Namespace $ns.Name}}selected="1"{{end}}>
								{{$ns.Caption}}
							</option>
						{{end}}
					</select>
				</td>
				<td class="search">
					{{if .Admin}}
						<a href="/admin">admin</a> |
					{{end}}
					{{if .LoginLink}}
						<a href="{{.LoginLink}}">sign-in</a> |
					{{end}}
					<a href="https://groups.google.com/forum/#!forum/syzkaller" target="_blank">mailing list</a> |
					<a href="https://github.com/google/syzkaller" target="_blank">source</a> |
					<a href="https://github.com/google/syzkaller/blob/master/docs/syzbot.md" target="_blank">docs</a>
				</td>
			</tr>
		</table>
	</header>
	<br>
{{end}}

{{/* List of bugs, invoked with *uiBugGroup */}}
{{define "bug_list"}}
{{if .}}
{{if .Bugs}}
<table class="list_table">
	{{if $.Fragment}}
		<caption id="{{$.Fragment}}"><a class="plain" href="#{{$.Fragment}}">
	{{else}}
		<caption>
	{{end}}
	{{$.Caption}} ({{len $.Bugs}}):
	{{if $.Fragment}}</a>{{end}}
	</caption>
	<thead>
	<tr>
		{{if $.ShowNamespace}}
			<th><a onclick="return sortTable(this, 'Kernel', textSort)" href="#">Kernel</a></th>
		{{end}}
		<th><a onclick="return sortTable(this, 'Title', textSort)" href="#">Title</a></th>
		<th><a onclick="return sortTable(this, 'Repro', reproSort)" href="#">Repro</a></th>
		<th><a onclick="return sortTable(this, 'Bisected', textSort)" href="#">Bisected</a></th>
		<th><a onclick="return sortTable(this, 'Count', numSort)" href="#">Count</a></th>
		<th><a onclick="return sortTable(this, 'Last', timeSort)" href="#">Last</a></th>
		<th><a onclick="return sortTable(this, 'Reported', timeSort)" href="#">Reported</a></th>
		{{if $.ShowPatch}}
			<th><a onclick="return sortTable(this, 'Closed', timeSort)" href="#">Closed</a></th>
			<th><a onclick="return sortTable(this, 'Patch', textSort)" href="#">Patch</a></th>
		{{end}}
		{{if $.ShowPatched}}
			<th><a onclick="return sortTable(this, 'Patched', patchedSort)" href="#">Patched</a></th>
		{{end}}
		{{if $.ShowStatus}}
			<th><a onclick="return sortTable(this, 'Status', textSort)" href="#">Status</a></th>
		{{end}}
	</tr>
	</thead>
	<tbody>
	{{range $b := .Bugs}}
		<tr>
			{{if $.ShowNamespace}}<td>{{$b.Namespace}}</td>{{end}}
			<td class="title"><a href="{{$b.Link}}">{{$b.Title}}</a></td>
			<td class="stat">{{formatReproLevel $b.ReproLevel}}</td>
			<td class="stat">
				{{if and $b.BisectCauseDone $b.BisectFixDone}}
					cause+fix
				{{else if $b.BisectCauseDone}}
					cause
				{{else if $b.BisectFixDone}}
					fix
				{{end}}
			</td>
			<td class="stat {{if $b.NumCrashesBad}}bad{{end}}">{{$b.NumCrashes}}</td>
			<td class="stat">{{formatLateness $.Now $b.LastTime}}</td>
			<td class="stat">
				{{if $b.ExternalLink}}
					<a href="{{$b.ExternalLink}}">{{formatLateness $.Now $b.ReportedTime}}</a>
				{{else}}
					{{formatLateness $.Now $b.ReportedTime}}
				{{end}}
			</td>
			{{if $.ShowPatch}}
				<td class="stat">{{formatLateness $.Now $b.ClosedTime}}</td>
				<td class="commit_list">{{template "fix_commits" $b.Commits}}</td>
			{{end}}
			{{if $.ShowPatched}}
				<td class="patched" {{if $b.Commits}}title="{{with $com := index $b.Commits 0}}{{$com.Title}}{{end}}"{{end}}>{{len $b.PatchedOn}}/{{$b.NumManagers}}</td>
			{{end}}
			{{if $.ShowStatus}}
				<td class="status">
					{{if $b.ExternalLink}}
						<a href="{{$b.ExternalLink}}">{{$b.Status}}</a>
					{{else}}
						{{$b.Status}}
					{{end}}
				</td>
			{{end}}
		</tr>
	{{end}}
	</tbody>
</table>
{{end}}
{{end}}
{{end}}

{{/* List of managers, invoked with []*uiManager */}}
{{define "manager_list"}}
{{if .}}
<table class="list_table">
	<caption id="managers"><a class="plain" href="managers">Instances:</a></caption>
	<thead>
	<tr>
		<th>Name</th>
		<th>Active</th>
		<th>Uptime</th>
		<th>Corpus</th>
		<th>Coverage</th>
		<th>Crashes</th>
		<th>Execs</th>
		<th colspan="3">Kernel build</th>
		<th colspan="3">syzkaller build</th>
	</tr>
	<tr>
		<th></th>
		<th></th>
		<th></th>
		<th></th>
		<th></th>
		<th></th>
		<th></th>
		<th>Commit</th>
		<th>Freshness</th>
		<th>Status</th>
		<th>Commit</th>
		<th>Freshness</th>
		<th>Status</th>
	</tr>
	</thead>
	<tbody>
	{{range $mgr := .}}
		<tr>
			<td>{{link $mgr.Link $mgr.Name}}</td>
			<td class="stat {{if $mgr.LastActiveBad}}bad{{end}}">{{formatLateness $mgr.Now $mgr.LastActive}}</td>
			<td class="stat">{{formatDuration $mgr.CurrentUpTime}}</td>
			<td class="stat">{{formatStat $mgr.MaxCorpus}}</td>
			<td class="stat">
				{{if $mgr.CoverLink}}
					<a href="{{$mgr.CoverLink}}" target="_blank">
				{{end}}
				{{formatStat $mgr.MaxCover}}
				{{if $mgr.CoverLink}}
					</a>
				{{end}}
			</td>
			<td class="stat">{{formatStat $mgr.TotalCrashes}}</td>
			{{if $mgr.TotalExecs}}
				<td class="stat">{{formatStat $mgr.TotalExecs}}</td>
			{{else}}
				<td class="stat bad">broken</td>
			{{end}}
			{{with $build := $mgr.CurrentBuild}}
				<td class="stat" title="[{{$build.KernelAlias}}] {{$build.KernelCommitTitle}}">{{link $build.KernelCommitLink (formatShortHash $build.KernelCommit)}}</td>
				<td class="stat" title="{{formatTime $build.KernelCommitDate}}" {{if $mgr.FailedBuildBugLink}}class="bad"{{end}}>{{formatLateness $mgr.Now $build.KernelCommitDate}}</td>
				<td class="stat">{{if $mgr.FailedBuildBugLink}}<a href="{{$mgr.FailedBuildBugLink}}" class="bad">failing</a>{{end}}</td>
				<td class="stat">{{link $build.SyzkallerCommitLink (formatShortHash $build.SyzkallerCommit)}}</td>
				<td class="stat" title="{{formatTime $build.SyzkallerCommitDate}}" {{if $mgr.FailedSyzBuildBugLink}}class="bad"{{end}}>{{formatLateness $mgr.Now $build.SyzkallerCommitDate}}</td>
				<td class="stat">{{if $mgr.FailedSyzBuildBugLink}}<a href="{{$mgr.FailedSyzBuildBugLink}}" class="bad">failing</a>{{end}}</td>
			{{else}}
				<td></td>
				<td></td>
				<td></td>
				<td></td>
				<td></td>
				<td></td>
			{{end}}
		</tr>
	{{end}}
	</tbody>
</table>
{{end}}
{{end}}

{{/* List of fixing commits, invoked with []*uiCommit */}}
{{define "fix_commits"}}
{{range $com := .}}
	<span class="mono">
		{{if $com.Hash}}
			{{formatShortHash $com.Hash}} 
		{{end}}
		{{link $com.Link $com.Title}}
	</span>
{{end}}
{{end}}

{{/* Bisection result, invoked with *uiJob */}}
{{/* Show bisection results */}}
{{define "bisect_results"}}
{{if .}}
	<br>
	{{$causeJob := 1}}
	{{$fixJob := 2}}
	{{if .ErrorLink}}
		{{if eq .Type $causeJob}}
			<b>Cause bisection: failed</b>
		{{else if eq .Type $fixJob}}
			<b>Fix bisection: failed</b>
		{{end}}
		({{link .LogLink "bisect log"}})</b><br>
	{{else if .Commit}}
		{{if eq .Type $causeJob}}
			<b>Cause bisection: introduced by</b>
		{{else if eq .Type $fixJob}}
			<b>Fix bisection: fixed by</b>
		{{end}}
		<b>({{link .LogLink "bisect log"}}):</b><br>
		<br><span class="mono">
		commit {{.Commit.Hash}}<br>
		Author: {{.Commit.Author}}<br>
		Date:   {{formatKernelTime .Commit.Date}}<br>
		<br>
		&nbsp;&nbsp;{{.Commit.Title}}<br>
		</span><br>
	{{else if .Commits}}
		{{if eq .Type $causeJob}}
			<b>Cause bisection: the cause commit could be any of</b>
		{{else if eq .Type $fixJob}}
			<b>Fix bisection: the fix commit could be any of</b>
		{{end}}
		<b>({{link .LogLink "bisect log"}}):</b><br>
		<br><span class="mono">
		{{range $com := .Commits}}
			&nbsp;&nbsp;{{formatTagHash $com.Hash}} {{$com.Title}}<br>
		{{end}}
		</span>
	{{else}}
		{{if eq .Type $causeJob}}
			<b>Cause bisection: the bug happens on the oldest tested release</b>
		{{else if eq .Type $fixJob}}
			<b>Fix bisection: the bug occurs on the latest tested release</b>
		{{end}}
		<br>
	{{end}}
	{{if .CrashLogLink}}
		Crash: {{link .CrashReportLink .CrashTitle}} ({{link .CrashLogLink "log"}})<br>
		Repro: {{optlink .Crash.ReproCLink "C"}}
		{{optlink .Crash.ReproSyzLink "syz"}}
		{{optlink .Crash.KernelConfigLink ".config"}}<br>
	{{end}}
	{{if not .Reported}}[report pending]<br>{{end}}
{{end}}
{{end}}

{{/* List of fixing commits, invoked with *uiCrashTable */}}
{{/* Show crashes */}}
{{define "crash_list"}}
{{if .}}
<table class="list_table">
	<caption>{{.Caption}}:</caption>
		<thead>
		<tr>
			<th><a onclick="return sortTable(this, 'Manager', textSort)" href="#">Manager</a></th>
			<th><a onclick="return sortTable(this, 'Time', textSort, true)" href="#">Time</a></th>
			<th><a onclick="return sortTable(this, 'Kernel', textSort)" href="#">Kernel</a></th>
			<th><a onclick="return sortTable(this, 'Commit', textSort)" href="#">Commit</a></th>
			<th><a onclick="return sortTable(this, 'Syzkaller', textSort)" href="#">Syzkaller</a></th>
			<th><a onclick="return sortTable(this, 'Config', textSort)" href="#">Config</a></th>
			<th><a onclick="return sortTable(this, 'Log', textSort)" href="#">Log</a></th>
			<th><a onclick="return sortTable(this, 'Report', reproSort)" href="#">Report</a></th>
			<th><a onclick="return sortTable(this, 'Syz repro', reproSort)" href="#">Syz repro</a></th>
			<th><a onclick="return sortTable(this, 'C repro', textSort)" href="#">C repro</a></th>
			{{if .HasMaintainers}}
			<th><a onclick="return sortTable(this, 'Maintainers', textSort)" href="#">Maintainers</a></th>
			{{end}}
		</tr>
		</thead>
		<tbody>
		{{range $b := .Crashes}}
		<tr>
			<td class="manager">{{$b.Manager}}</td>
			<td class="time">{{formatTime $b.Time}}</td>
			<td class="kernel" title="{{$b.KernelAlias}}">{{$b.KernelAlias}}</td>
			<td class="tag" title="{{$b.KernelCommit}}
	{{formatTime $b.KernelCommitDate}}">{{link $b.KernelCommitLink (formatShortHash $b.KernelCommit)}}</td>
			<td class="tag">{{link $b.SyzkallerCommitLink (formatShortHash $b.SyzkallerCommit)}}</td>
			<td class="config">{{if $b.KernelConfigLink}}<a href="{{$b.KernelConfigLink}}">.config</a>{{end}}</td>
			<td class="repro">{{if $b.LogLink}}<a href="{{$b.LogLink}}">log</a>{{end}}</td>
			<td class="repro">{{if $b.ReportLink}}<a href="{{$b.ReportLink}}">report</a>{{end}}</td>
			<td class="repro">{{if $b.ReproSyzLink}}<a href="{{$b.ReproSyzLink}}">syz</a>{{end}}</td>
			<td class="repro">{{if $b.ReproCLink}}<a href="{{$b.ReproCLink}}">C</a>{{end}}</td>
			{{if $.HasMaintainers}}
			<td class="maintainers" title="{{$b.Maintainers}}">{{$b.Maintainers}}</td>
			{{end}}
		</tr>
		{{end}}
		</tbody>
</table>
{{end}}
{{end}}
